package top.superflow.flow.validate

import top.superflow.exception.Exceptable
import top.superflow.flow.config.{FlowConfig, RouteConfig}
import top.superflow.lang.{ArrayUtils, CollectionUtils}
import top.superflow.log.Loggable

class FlowValidator extends ConfigValidator[FlowConfig] with Loggable with Exceptable{
  
  def isValid(flowConfig : FlowConfig) : Boolean = {
    if(flowConfig == null) throw new ValidationException("flow configuration should not be null!");


    if(flowConfig.getStart == null){
      throwRequestUnsupportedException("There is no start for the flow [{}]", flowConfig.getKey);
    }

    if(CollectionUtils.isEmpty(flowConfig.getRoutes)){
      throwRequestUnsupportedException( "There is no route configured for the flow [{}]", flowConfig.getKey)
    }

    val routes = flowConfig.getRoutes
    ValidatorFactory.getValidator(routes).asInstanceOf[ConfigValidator[Array[RouteConfig]]].isValid(routes)

    true
  }
  
  /**
   * make sure it's certain to determine unique of the route flow only by the source point and target point
   * e.g. if on process has been used multiple times in the flow, there is no way to determine the whole flow only by the source and target
   * in such case, need to add extra information of post route in the specific route which contains a target process which is used more than once in the flow
   * sum: if all process has been used only once in the flow, then the information of post route is not needed. Otherwise post routes information is necessary
   */
  private def validateRouteCertainty(flowConfig : FlowConfig) = {
//    if(isSimpleFlow(flowConfig)){
//      validateSimpleFlow(flowConfig)
//    }else{
//      validateComplicatedFlow(flowConfig)
//    }
  }
  
  private def validateSimpleFlow(flowConfig : FlowConfig){
    val startNode = findStart(flowConfig)
  }
  
  private def findStart(flowConfig : FlowConfig) : String = {
    
    null
  }
  
  private def validateComplicatedFlow(flowConfig : FlowConfig){
    
  }
  
//  private def isSimpleFlow(flowConfig : FlowConfig) : Boolean = {
//    logger.info("The flow [" + flowConfig.getKey  + "] is considered a simple flow as there is no start configured. ")
//  }

}